package org.vacoor.nothing.ui.util;

import javax.swing.*;
import java.awt.*;
import java.awt.image.BufferedImage;

/**
 * 图像绘制工具,一般在UI绘制使用
 *
 * @author Vacoor
 */
public class ImagePaintUtil {
    /**
     * 将图片切割后绘制,可以将一个小图片切割后绘制,中间拉伸
     *
     * @param g           绘制使用的Graphics对象
     * @param image       要绘制的图像
     * @param imageInsets 图像中不拉伸的边界区域
     * @param paintRect   绘制的目标区域
     */
    public static void paintImage(Graphics g, BufferedImage image, Insets imageInsets, Rectangle paintRect) {
        int x = paintRect.x;
        int y = paintRect.y;
        int width = paintRect.width;
        int height = paintRect.height;

        if ((width <= 0) || (height <= 0) || (x + width <= 0)
                || (y + height <= 0)) {
            return;
        }

        Graphics2D g2d = (Graphics2D) g;
        // 保存原算法
        Object oldHintValue = g2d.getRenderingHint(RenderingHints.KEY_ANTIALIASING);
        int imageLeft = imageInsets.left;
        int imageRight = imageInsets.right;
        int imageTop = imageInsets.top;
        int imageBottom = imageInsets.bottom;
        int imageWidth = image.getWidth();
        int imageHeight = image.getHeight();

        g2d.setRenderingHint(RenderingHints.KEY_ANTIALIASING, RenderingHints.VALUE_ANTIALIAS_ON);
        g2d.translate(x, y);

        // 绘制左上
        g2d.drawImage(image, 0, 0, imageLeft, imageTop, 0, 0, imageLeft, imageTop, null);
        // 绘制顶部
        g2d.drawImage(image, imageLeft, 0, width - imageRight, imageTop, imageLeft, 0, imageWidth - imageRight, imageTop, null);
        // 绘制右上
        g2d.drawImage(image, width - imageRight, 0, width, imageTop, imageWidth - imageRight, 0, imageWidth, imageTop, null);

        // 绘制左侧
        g2d.drawImage(image, 0, imageTop, imageLeft, height - imageBottom, 0, imageTop, imageLeft, imageHeight - imageBottom, null);
        // 绘制中间
        g2d.drawImage(image, imageLeft, imageTop, width - imageRight, height - imageBottom, imageLeft, imageTop, imageWidth - imageRight, imageHeight - imageBottom, null);
        // 绘制右侧
        g2d.drawImage(image, width - imageRight, imageTop, width, height - imageBottom, imageWidth - imageRight, imageTop, imageWidth, imageHeight - imageBottom, null);
        // 绘制左下
        g2d.drawImage(image, 0, height - imageBottom, imageLeft, height, 0, imageHeight - imageBottom, imageLeft, imageHeight, null);
        // 底部
        g2d.drawImage(image, imageLeft, height - imageBottom, width - imageRight, height, imageLeft, imageHeight - imageBottom, imageWidth - imageRight, imageHeight, null);
        // 右下
        g2d.drawImage(image, width - imageRight, height - imageBottom, width, height, imageWidth - imageRight, imageHeight - imageBottom, imageWidth, imageHeight, null);
        g2d.translate(-x, -y);
        g2d.setRenderingHint(RenderingHints.KEY_ANTIALIASING, oldHintValue);
    }

    /**
     * 给指定的组件绘制背景图片/背景颜色
     *
     * @param g             绘制所使用的Graphics
     * @param component     要绘制的目标组件
     * @param background    背景色
     * @param image         要绘制的图像
     * @param imageOnly     是否只绘制图像而不绘制其他背景,如果为true,则背景颜色可以为null
     * @param alpha         绘制的透明度
     * @param visibleInsets 图像中不绘制的边框区域,有些图像边框为透明区域,不需要绘制
     * @param zoomImage     是否拉伸绘制,当图像大小不合适时候,是否进行拉伸
     */
    public static void paintBackground(Graphics g, JComponent component, Color background, BufferedImage image, boolean imageOnly, float alpha, Insets visibleInsets, boolean zoomImage) {
        if ((alpha > 0.0D) && ((!imageOnly) || (image != null))) {
            Graphics2D g2d = (Graphics2D) g;
            Composite oldComposite = g2d.getComposite();
            g2d.setComposite(AlphaComposite.SrcOver.derive(alpha));

            // 如果不是只绘制图像,先绘制背景色
            if (!imageOnly) {
                Color oldColor = g2d.getColor();
                g2d.setColor(background);
                g2d.fillRect(visibleInsets.left, visibleInsets.top,
                        component.getWidth() - visibleInsets.left
                                - visibleInsets.right, component.getHeight()
                        - visibleInsets.top - visibleInsets.bottom);
                g2d.setColor(oldColor);
            }

            if (image != null) {
                Object oldHintValue = g2d
                        .getRenderingHint(RenderingHints.KEY_ANTIALIASING);
                g2d.setRenderingHint(RenderingHints.KEY_ANTIALIASING,
                        RenderingHints.VALUE_ANTIALIAS_ON);
                if (zoomImage) {
                    g2d.drawImage(image, visibleInsets.left, visibleInsets.top,
                            component.getWidth() - visibleInsets.left
                                    - visibleInsets.right,
                            component.getHeight() - visibleInsets.top
                                    - visibleInsets.bottom, component);
                } else {
                    g2d.drawImage(image, visibleInsets.left, visibleInsets.top,
                            component.getWidth() - visibleInsets.right,
                            component.getHeight() - visibleInsets.bottom,
                            visibleInsets.left, visibleInsets.top,
                            component.getWidth() - visibleInsets.right,
                            component.getHeight() - visibleInsets.bottom,
                            component);
                }
                g2d.setRenderingHint(RenderingHints.KEY_ANTIALIASING,
                        oldHintValue);
            }
            g2d.setComposite(oldComposite);
        }
    }
}
